package net.dntuan.training.spring.security;

import java.util.ArrayList;
import java.util.List;

import javax.servlet.http.HttpServletRequest;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.security.authentication.AuthenticationProvider;
import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.AuthenticationException;
import org.springframework.security.core.GrantedAuthority;
import org.springframework.security.core.userdetails.User;
import org.springframework.stereotype.Component;
import org.springframework.web.context.request.RequestContextHolder;
import org.springframework.web.context.request.ServletRequestAttributes;

@Component("dbAuthenticationProvider")
public class DBAuthenticationProvider implements AuthenticationProvider {

	private static final Logger logger = LoggerFactory.getLogger(DBAuthenticationProvider.class);

	public DBAuthenticationProvider() {
		logger.debug("initialize bean");
	}

	// TODO improve this bean by in-memory userDetailsService
	@Override
	public Authentication authenticate(Authentication authentication) throws AuthenticationException {
		String username = (String) authentication.getPrincipal();
		String password = (String) authentication.getCredentials();
		MyWebAuthenticationDetails details = (MyWebAuthenticationDetails) authentication.getDetails();
		if (details == null) {
			// in case of basic-authentication
			HttpServletRequest request = ((ServletRequestAttributes) RequestContextHolder.currentRequestAttributes()).getRequest();
			details = new MyWebAuthenticationDetails(request);
		}
		logger.debug("entered username: " + username);
		logger.debug("entered password: " + password);
		logger.debug(details == null ? "Couldn't get MyWebAuthenticationDetails" : "appId: " + details.getAppId());

		Authentication auth = null;
		if ("user".equalsIgnoreCase(username) || "superuser".equalsIgnoreCase(username)) {
			List<GrantedAuthority> roles = new ArrayList<GrantedAuthority>();
			User user = new User(username, password, roles);
			auth = new UsernamePasswordAuthenticationToken(user, null, roles);
		}
		return auth;
	}

	@Override
	public boolean supports(Class<?> authentication) {
		return true;
	}

}
